﻿using System;
using System.Data;
using System.Data.SqlClient;
using System.Windows.Forms;
using System.Collections.Generic;
using DataCenter.Interface.Model;
using System.Text.RegularExpressions;

namespace DataCenter.Utility
{
    public partial class ObjectEditForm : Form
    {
        private ObjectEditForm()
        {
            InitializeComponent();
        }
        public ObjectEditForm(SqlCommand command)
            : this()
        {
            this._Command = command;
        }
        public ObjectEditForm(SqlCommand command, ObjectEntity entity)
            : this(command)
        {
            this.entity = entity;
            this.IsModify = true;
        }
        private bool IsModify = false;
        private SqlCommand _Command;
        private Dictionary<int, ComboBoxItem> DictTypeItem;
        private Dictionary<int, ComboBoxItem> DictComponentItem;

        private ObjectEntity entity;
        public ObjectEntity Entity
        {
            get { return entity; }
            set { entity = value; }
        }

        private void ObjectEditForm_Load(object sender, EventArgs e)
        {
            if (!IsModify)
            {
                txtObjectId.Text = Convert.ToString(ObjectEntity.SearchMaxId(_Command) + 1);
            }
            else
            {
                txtObjectId.Enabled = false;
                ShowObjectEntity();
            }
        }

        private void cboSource_SelectedIndexChanged(object sender, EventArgs e)
        {
            cboAdapter.Enabled = (cboSource.SelectedIndex > 0);
        }

        private void cboCalculator_SelectedIndexChanged(object sender, EventArgs e)
        {
            txtObjectKey.Enabled = (cboCalculator.SelectedIndex == 0);
            txtExpression.Enabled = (cboCalculator.SelectedIndex > 0);
            grpImport.Enabled = (cboCalculator.SelectedIndex == 0);
            grpProcess.Enabled = (cboCalculator.SelectedIndex == 0);
        }

        private void btnOk_Click(object sender, EventArgs e)
        {
            if (Check())
            {                
                if (!IsModify)
                {
                    entity = GetObjectEntity(null);
                    entity.Create(_Command);
                }
                else
                {
                    entity = GetObjectEntity(entity);
                    entity.Modify(_Command);
                }

                this.DialogResult = DialogResult.OK;
                this.Close();
            }
        }

        public bool InitForm(Dictionary<int, string> dictType,
            Dictionary<int, ComponentEntity> dictComponent)
        {
            DictTypeItem = new Dictionary<int, ComboBoxItem>();
            DictComponentItem = new Dictionary<int, ComboBoxItem>();

            cboObjectType.Items.Clear();
            foreach (KeyValuePair<int, string> typePair in dictType)
            {
                string text = typePair.Value + "(" + typePair.Key + ")";
                ComboBoxItem item = new ComboBoxItem(text, typePair.Key);
                cboObjectType.Items.Add(item);

                if (!DictTypeItem.ContainsKey(typePair.Key))
                    DictTypeItem.Add(typePair.Key, item);
            }

            cboSource.Items.Clear();
            cboAdapter.Items.Clear();
            cboProccessor.Items.Clear();
            cboCalculator.Items.Clear();

            cboSource.Items.Add("无");
            cboProccessor.Items.Add("无");
            cboCalculator.Items.Add("无");

            foreach (ComponentEntity component in dictComponent.Values)
            {
                string text = component.ComponentName + "(" + component.ComponentId + ")";
                ComboBoxItem item = new ComboBoxItem(text, component);

                switch (component.ComponentType)
                {
                    case ComponentTypes.Source: cboSource.Items.Add(item); break;
                    case ComponentTypes.Adapter: cboAdapter.Items.Add(item); break;
                    case ComponentTypes.Processor: cboProccessor.Items.Add(item); break;
                    case ComponentTypes.Calculator: cboCalculator.Items.Add(item); break;
                }

                if (!DictComponentItem.ContainsKey(component.ComponentId))
                    DictComponentItem.Add(component.ComponentId, item);
            }

            if (cboObjectType.Items.Count > 0)
                cboObjectType.SelectedIndex = 0;
            cboSource.SelectedIndex = 0;
            cboProccessor.SelectedIndex = 0;
            cboCalculator.SelectedIndex = 0;

            return true;
        }

        private bool Check()
        {
            bool checkResult = true;
            string errmsg = "";
            Control ctrl = null;

            int iValue;
            double dValue;

            if (string.IsNullOrEmpty(txtObjectId.Text))
            {
                errmsg = "对象编号不能为空";
                ctrl = txtObjectId;
                goto ShowError;
            }
            if (!int.TryParse(txtObjectId.Text, out iValue))
            {
                errmsg = "对象编号必须为有效的整数";
                ctrl = txtObjectId;
                goto ShowError;
            }
            if (!int.TryParse(txtObjectId.Text, out iValue))
            {
                errmsg = "对象编号必须为有效的整数";
                ctrl = txtObjectId;
                goto ShowError;
            }
            if (!IsModify && ObjectEntity.CheckRepeat(_Command, iValue))
            {
                errmsg = string.Format("对象编号{0}已经存在", iValue);
                ctrl = txtObjectId;
                goto ShowError;
            }

            if (string.IsNullOrEmpty(txtObjectName.Text))
            {
                errmsg = "对象名称不能为空";
                ctrl = txtObjectName;
                goto ShowError;
            }

            if (!string.IsNullOrEmpty(txtDefaultValue.Text))
            {
                if (!double.TryParse(txtDefaultValue.Text, out dValue))
                {
                    errmsg = "默认值必须为有效的浮点数";
                    ctrl = txtDefaultValue;
                    goto ShowError;
                }
            }

            if (!string.IsNullOrEmpty(txtUnit.Text))
            {
                if (!double.TryParse(txtUnit.Text, out dValue))
                {
                    errmsg = "单位系数必须为有效的浮点数";
                    ctrl = txtUnit;
                    goto ShowError;
                }
            }

            int indexCount = 0;
            if (cboCalculator.SelectedIndex == 0)
            {
                if (cboSource.SelectedIndex > 0)
                {
                    if (cboAdapter.SelectedIndex < 0)
                    {
                        errmsg = "请选择一个对象适配器";
                        ctrl = cboAdapter;
                        goto ShowError;
                    }
                    else
                    {
                        indexCount += cboAdapter.SelectedIndex;
                    }
                }
                if (string.IsNullOrEmpty(txtObjectKey.Text))
                {
                    errmsg = "对象主键不能为空";
                    ctrl = txtObjectKey;
                    goto ShowError;
                }

                indexCount += cboProccessor.SelectedIndex;
            }
            else
            {
                if (string.IsNullOrEmpty(txtExpression.Text))
                {
                    errmsg = "对象计算表达式不能为空";
                    ctrl = txtExpression;
                    goto ShowError;
                }

                indexCount += cboCalculator.SelectedIndex;
            }

            if (indexCount == 0)
            {
                errmsg = "至少选择一个对象处理方式";
                goto ShowError;
            }

        ShowError:
            if (!string.IsNullOrEmpty(errmsg))
            {
                MessageBox.Show(errmsg, this.Text, MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
                if (ctrl != null) ctrl.Focus();
                checkResult = false;
            }

            return checkResult;
        }

        private ObjectEntity GetObjectEntity(ObjectEntity objectEntity)
        {
            ObjectEntity entity = objectEntity;
            if (entity == null) entity = new ObjectEntity();            

            entity.ObjectId = Convert.ToInt32(txtObjectId.Text);
            entity.ObjectName = txtObjectName.Text.Trim();
            entity.ObjectType = Convert.ToInt32(((ComboBoxItem)cboObjectType.SelectedItem).Tag);
            if (!string.IsNullOrEmpty(txtDefaultValue.Text))
            {
                entity.DefaultValue = Convert.ToSingle(txtDefaultValue.Text);
            }
            if (!string.IsNullOrEmpty(txtUnit.Text))
            {
                entity.Unit = Convert.ToSingle(txtUnit.Text);
            }
            if (cboCalculator.SelectedIndex > 0)
            {
                entity.IsVirtual = true;
                entity.BindingCalculatorId = ((ComponentEntity)((ComboBoxItem)cboCalculator.SelectedItem).Tag).ComponentId;
                entity.ObjectKey = txtExpression.Text.Trim();

                entity.BindingSourceId = -1;
                entity.BindingAdapterId = -1;
                entity.BindingProcessorId = -1;
            }
            else
            {
                if (cboSource.SelectedIndex > 0)
                {
                    entity.BindingSourceId = ((ComponentEntity)((ComboBoxItem)cboSource.SelectedItem).Tag).ComponentId;
                    entity.BindingAdapterId = ((ComponentEntity)((ComboBoxItem)cboAdapter.SelectedItem).Tag).ComponentId;
                }
                if (cboProccessor.SelectedIndex > 0)
                {
                    entity.BindingProcessorId = ((ComponentEntity)((ComboBoxItem)cboProccessor.SelectedItem).Tag).ComponentId;
                }

                entity.ObjectKey = txtObjectKey.Text.Trim();
                entity.BindingCalculatorId = -1;
            }

            return entity;
        }
        private void ShowObjectEntity()
        {
            txtObjectId.Text = entity.ObjectId.ToString();
            txtObjectName.Text = entity.ObjectName;

            if (DictTypeItem.ContainsKey(entity.ObjectType))
            {
                cboObjectType.SelectedItem = DictTypeItem[entity.ObjectType];
            }

            txtDefaultValue.Text = entity.DefaultValue.ToString();
            txtUnit.Text = entity.Unit.ToString();

            if (entity.CanCalculate)
            {
                txtExpression.Text = entity.ObjectKey;

                if (DictComponentItem.ContainsKey(entity.BindingCalculatorId))
                {
                    cboCalculator.SelectedItem = DictComponentItem[entity.BindingCalculatorId];
                }
            }
            else
            {
                txtObjectKey.Text = entity.ObjectKey;

                if (entity.CanImport)
                {
                    if (DictComponentItem.ContainsKey(entity.BindingSourceId))
                    {
                        cboSource.SelectedItem = DictComponentItem[entity.BindingSourceId];
                    }
                    if (DictComponentItem.ContainsKey(entity.BindingAdapterId))
                    {
                        cboAdapter.SelectedItem = DictComponentItem[entity.BindingAdapterId];
                    }
                }
                if (entity.CanProcess)
                {
                    if (DictComponentItem.ContainsKey(entity.BindingProcessorId))
                    {
                        cboProccessor.SelectedItem = DictComponentItem[entity.BindingProcessorId];
                    }
                }
            }
        }
    }
}
